#include "utils.h"
#include "oper.h"
#include "supp.h"

int Data_Processing_Instr_reg(ARMProcState *ARMProc){ 

	unsigned int instr = ARMProc->CurInstr;
	unsigned int Op1 = BITS(instr,20,24);
	unsigned int Op2 = 0;
	unsigned int Op3 = 0;

	switch(Op1){ 

		case 0x0:
		case 0x1:
			/*Bitwise AND Operation On AND A8-36*/
			ARM_Instr_Debug(("And_Oper REG_INSTR\n"));
			data_proc_oper(ARMProc,REG_INSTR,AND_OPERATION);
			break;
		case 0x2:
		case 0x3:
			/*Bitwise Exclusive OR On EOR A8-96*/
			data_proc_oper(ARMProc,REG_INSTR,EOR_OPERATION);
			break;
		case 0x4:
		case 0x5:
			/*Bitwise Substract On SUB A8-422*/
			data_proc_oper(ARMProc,REG_INSTR,SUBTRACT_OPERATION);
			break;
		case 0x6:
		case 0x7:
			/*Reverse Substract On RSB A8-286*/
			data_proc_oper(ARMProc,REG_INSTR,REVERSE_SUBTRACT_OPERATION);
			break;

		case 0x8:
		case 0x9:
			/* Add Operation On ADD A8-24 */
			data_proc_oper(ARMProc,REG_INSTR,ADD_OPERATION);
			break;

		case 0xA:
		case 0xB:
			/*Add with Carry On ADC A8-16*/
			data_proc_oper(ARMProc,REG_INSTR,ADD_WITH_CARRY_OPERATION);
			break;

		case 0xC:
		case 0xD:
			/* Subtract with Carry (SBC) On A8-304*/
			data_proc_oper(ARMProc,REG_INSTR,SUBTRACT_WITH_CARRY_OPERATION);
			break;
		case 0xE:
		case 0xF:
			/*Reverse Subtract with Carry (RSC) On A8-292*/
			data_proc_oper(ARMProc,REG_INSTR,REVERSE_SUBTRACT_WITH_CARRY_OPERATION);
			break;

		case 0x11:
			/*Test (TST) On A8-456*/
			data_proc_oper(ARMProc,REG_INSTR,TEST_OPERATION);
			break;
		case 0x13:
			/*Test Equivalence (TEQ) On A8-450*/
			data_proc_oper(ARMProc,REG_INSTR,TEST_EQUIVALENCE_OPERATION);
			break;

		case 0x15:
			/*Compare (CMP) On A8-82*/
			data_proc_oper(ARMProc,REG_INSTR,COMPARE_OPERATION);
			break;
		case 0x17:
			/*Compare Negative (CMN) On A8-76*/
			data_proc_oper(ARMProc,REG_INSTR,COMPARE_NEGATIVE_OPERATION);
			break;

		case 0x18:
		case 0x19:
			/*Bitwise OR (ORR) On A8-230 */
			data_proc_oper(ARMProc,REG_INSTR,OR_OPERATION);
			break;

		case 0x1A:
		case 0x1B:
			/*Move and Shift Operation */
			Op2 = BITS(instr,7,11);
			Op3 = BITS(instr,5,6);

			if(0 == Op2){ 
				if(0 == Op3){ 
					data_proc_oper(ARMProc,REG_INSTR,MOVE_OPERATION);
					/*Move (MOV) register A8-196*/
					break;
				}
				else if(0x3 == Op3){ 
					/*Rotate Right with Extend (RRX) On A8-282*/
					data_proc_oper(ARMProc,REG_INSTR,ROTATE_RIGHT_WITH_EXTEND_OPERATION);
					break;
				}
				else { 
					/* Exception */
					break;
				}
				break;
			}
			else { 
				if((0x0 == Op3) && (0 != Op2)){ 
					/*Logical Shift Right (LSL) On A8-178*/
					data_proc_oper(ARMProc,REG_INSTR,LOGICAL_SHIFT_RIGHT_OPERATION);
					break;
				}
				else if((0x3 == Op3) && (0 != Op2)){ 
					/*Rotate Right (ROR) On A8-278*/
					data_proc_oper(ARMProc,REG_INSTR,ROTATE_RIGHT_OPERATION);
					break;
				}
				else if(0x1 == Op3){ 
					/*Logical Shift Right LSR On A8-182*/
					data_proc_oper(ARMProc,REG_INSTR,LOGICAL_SHIFT_RIGHT_OPERATION);
					break;
				}
				else if(0x2 == Op3){ 
					/*Arithmetric Shift Right ASR On A8-40*/
					data_proc_oper(ARMProc,REG_INSTR,ARITHMETRIC_SHIFT_RIGHT_OPERATION);
					break;
				}
				else { 
					/* Exception */
					break;
				}
			}
			break;

		case 0x1C:
		case 0x1D:
			/*Bitwise Bit Clear BIC (register) on A8-52*/
			data_proc_oper(ARMProc,REG_INSTR,BIT_CLEAR_OPERATION);
			break;

		case 0x1E:
		case 0x1F:
			/*Bitwise Not MVN(register) On A8-216 */
			data_proc_oper(ARMProc,REG_INSTR,NOT_OPERATION);
			break;

		default:
			/*exception*/
			break;
	}

}

int Data_Processing_Instr_Shifted_reg(ARMProcState *ARMProc){ 
	
	unsigned int instr = ARMProc->CurInstr;
	unsigned int Op1 = BITS(instr,20,24);
	unsigned int Op2 = 0;

	switch(Op1){

		case 0x0:
		case 0x1:
			/*Bitwise AND Operation On AND A8-38*/
			data_proc_oper(ARMProc,SHIFTED_REG_INSTR,AND_OPERATION);
			break;
		case 0x2:
		case 0x3:
			/*Bitwise Exclusive OR On EOR A8-98*/
			break;
		case 0x4:
		case 0x5:
			/*Bitwise Substract On SUB A8-424*/
			break;
		case 0x6:
		case 0x7:
			/*Reverse Substract On RSB A8-288*/
			break;

		case 0x8:
		case 0x9:
			/* Add Operation On ADD A8-26 */
			break;

		case 0xA:
		case 0xB:
			/*Add with Carry On ADC A8-18*/
			break;

		case 0xC:
		case 0xD:
			/* Subtract with Carry (SBC) On A8-306*/
			break;
		case 0xE:
		case 0xF:
			/*Reverse Subtract with Carry (RSC) On A8-294*/
			break;

		case 0x11:
			/*Test (TST) On A8-458*/
			break;
		case 0x13:
			/*Test Equivalence (TEQ) On A8-452*/
			break;

		case 0x15:
			/*Compare (CMP) On A8-84*/
			break;
		case 0x17:
			/*Compare Negative (CMN) On A8-78*/
			break;

		case 0x18:
		case 0x19:
			/*Bitwise OR (ORR) On A8-232 */
			break;

		case 0x1A:
		case 0x1B:
			Op2 = BITS(instr,5,6);
			/* Shift Operations */
			if(0 == Op2){ 
				/*Logical Shift Left LSL(register) A8-180*/
				break;
			}
			else if(1 == Op2){ 
				/*Logical Shift Right LSR(register) A8-184*/
				break;
			}
			else if(2 == Op2){ 
				/*Arithmetic Shift Right ASR(register) A8-42*/
				break;
			}
			else if(3 == Op2){ 
				/*Rotate Right ROR(register) A8-280*/
				break;
			}
			else{ 
				/*exception*/
				break;
			}

			break;


		case 0x1C:
		case 0x1D:
			/*Bitwise Bit Clear BIC(register Shifted register) On A8-54*/
			break;

		case 0x1E:
		case 0x1F:
			/*Bitwise Not MVN (register shifted register) On A8-218*/
			break;

		default:
			/*Exception */
			break;
	}
}


int Data_Processing_Instr_Imm(ARMProcState *ARMProc){ 


	unsigned int instr = ARMProc->CurInstr;
	unsigned int Op = BITS(instr,20,24);
	unsigned int Rn = 0;
	/* These instructions all have modified immediate constants rather than a simple 12bit binary number This provides a more useful range of values  For detail See A5-9*/

	switch(Op){ 

		case 0x0:
		case 0x1:
			/*Bitwise AND AND(imm) On A8-34*/
			data_proc_oper(ARMProc,IMM_INSTR,AND_OPERATION);
			break;

		case 0x2:
		case 0x3:
			/*Bitwise Exclusive OR EOR(Imm) On A8-94*/
			break;

		case 0x4:
		case 0x5:
			Rn = BITS(instr,16,19);
			if(0xf == Rn){ 
				/*Form PC-related address ADR On A8-32*/
				break;
			}
			else { 
				/*Subtract SUB (imm)On A8-420*/
				break;
			}

		case 0x6:
		case 0x7:
			/*Reverse Subtract RSB (imm) On A8-284*/
			break;

		case 0x8:
		case 0x9:
			Rn = BITS(instr,16,19);
			if(0xf == Rn){ 
				/*Form PC-relative address ADR On A8-32*/
				break;
			}
			else { 
				/*Add ADD(imm,ARM) On A8-22*/
				break;
			}

		case 0xA:
		case 0xB:
			/*Add with Carry (ADC) On A8-14*/
			break;

		case 0xC:
		case 0xD:
			/*Subtract with Carry (SBC) On A8-302*/
			break;

		case 0xE:
		case 0xF:
			/*Reverse Subtract with Carry (RSC) On A8-290*/
			break;

		case 0x11:
			/*Test (TST) (imm) On A8-454*/
			break;

		case 0x13:
			/*Test Equivalence TEQ(Imm) On A8-448*/
			break;
		case 0x15:
			/*Compare CMP(Imm) A8-80*/
			break;
		case 0x17:
			/*Compare Negative CMN(Imm) A8-74*/
			break;
		
		case 0x18:
		case 0x19:
			/*Bitwise OR ORR(Imm) A8-228*/
			break;

		case 0x1A:
		case 0x1B:
			/*Move MOV(Imm) On A8-194*/
			break;

		case 0x1C:
		case 0x1D:
			/*Bitwise Bit Clear BIC(Imm) On A8-50*/
			break;

		case 0x1E:
		case 0x1F:
			/*Bitwise NOT MVN(Imm) On A8-214*/
			break;

		
	}
}


int data_proc_oper(ARMProcState *ARMProc,int mode,unsigned int Oper){ 

	unsigned int instr = ARMProc->CurInstr;
	int SFlag = BIT(instr,20);
	unsigned int Reg_Shift = 0;
	unsigned int Imm_Shift = 0;
	unsigned int Reg_Value = 0;
	unsigned int Shift_OperMode = NO_SHIFT_OPER;
	unsigned int Shift = 0;
	unsigned int Rm = 0;
	unsigned int Rn = 0;
	unsigned int Rd = 0;
	unsigned int Imm = 0;

	ARMProc->SFlag = SFlag;
	
				if(REG_INSTR == mode){ 

					Shift = BITS(instr,5,6);
					Imm_Shift = BITS(instr,7,11);
					Rm = BITS(instr,0,3);

					if(Shift == 0){ 
						if(0 == Imm_Shift){ 
							Shift_OperMode = NO_SHIFT_OPER;
						}
						else{ 
							Shift_OperMode = LSL_OPER;
							Shift_Oper(ARMProc,Shift_OperMode,Rm,Imm_Shift,SHIFT_IMM);
						}
					}
					else if(3 == Shift){ 
						if(0 == Imm_Shift){ 
							Shift_OperMode = RRX_OPER;
							Imm_Shift = 1;
							Shift_Oper(ARMProc,Shift_OperMode,Rm,Imm_Shift,SHIFT_IMM);
						}
						else { 
							Shift_OperMode = LSR_OPER;
							Shift_Oper(ARMProc,Shift_OperMode,Rm,Imm_Shift,SHIFT_IMM);
						}

					}
					else if(0x2 == Shift){ 
						Shift_OperMode = ASR_OPER;
						if(0 == Imm_Shift){ 
							Imm_Shift = 32;
						}
						Shift_Oper(ARMProc,Shift_OperMode,Rm,Imm_Shift,SHIFT_IMM);
					}
					else if(0x1 == Shift){ 
						Shift_OperMode = LSR_OPER;
						if(0 == Imm_Shift){ 
							Imm_Shift = 32;
						}	
						Shift_Oper(ARMProc,Shift_OperMode,Rm,Imm_Shift,SHIFT_IMM);
					}

					else { 
					/* Exception */
					}

					Rn = BITS(instr,16,19);
					Rd = BITS(instr,12,15);
					data_proc_oper_reg(ARMProc,Rd,Rn,Rm,Oper);
				}


				else if(SHIFTED_REG_INSTR == mode){ 
					
					Shift = BITS(instr,5,6);
					Reg_Shift = BITS(instr,8,11);
					Rm = BITS(instr,0,3);

					if(0 == Shift){ 
						Shift_OperMode = LSL_OPER;	
					}
					else {
						if(5 == Shift){ 
							And_Oper_Debug(("Reg Shift Oper Error\n"));
						//	return;
						}
						else { 
							Shift_OperMode = Shift;
						}
					}
					if(15 == Reg_Shift){ 
						And_Oper_Debug(("Reg Shift Rm interval Error\n"));
					//	return;
					}
					Reg_Value = ARMProc->Reg[Reg_Shift];
					Shift_Oper(ARMProc,Shift_OperMode,Rm,Reg_Shift,SHIFT_REG);

					Rn = BITS(instr,16,19);
					Rd = BITS(instr,12,15);
					data_proc_oper_reg(ARMProc,Rd,Rn,Rm,Oper);
				}

				else if(IMM_INSTR == mode){ 
					Rn = BITS(instr,16,19);
					Rd = BITS(instr,12,15);
					Imm = BITS(instr,0,11);
					And_oper_imm(ARMProc,Rd,Rn,Imm);
				}

				else { 
					/*Exception*/
				}


}

int data_proc_oper_reg(ARMProcState *ARMProc, unsigned int Dest, unsigned int Src1,unsigned int Src2,unsigned int Oper){ 

	switch(Oper){ 

		case AND_OPERATION:
			And_oper_reg(ARMProc,Dest,Src1,Src2);	
			break;
		case EOR_OPERATION:
			eor_oper_reg(ARMProc,Dest,Src1,Src2);
			break;
		case SUBTRACT_OPERATION:
			sub_oper_reg(ARMProc,Dest,Src1,Src2);	
			break;

		case REVERSE_SUBTRACT_OPERATION:
			rsb_oper_reg(ARMProc,Dest,Src1,Src2);
			break;
		case ADD_OPERATION:
			add_oper_reg(ARMProc,Dest,Src1,Src2);
			break;
		case ADD_WITH_CARRY_OPERATION: 
			adc_oper_reg(ARMProc,Dest,Src1,Src2);
			break;
		case SUBTRACT_WITH_CARRY_OPERATION:
			sbc_oper_reg(ARMProc,Dest,Src1,Src2);
			break;

		case REVERSE_SUBTRACT_WITH_CARRY_OPERATION:
			rsc_oper_reg(ARMProc,Dest,Src1,Src2);
			break;

		case TEST_OPERATION:
			tst_oper_reg(ARMProc,Dest,Src1,Src2);
			break;

		default:
			break;

	}
}

int data_proc_oper_imm(ARMProcState *ARMProc, unsigned int Dest, unsigned int Src1, unsigned int Src2, unsigned int Oper){ 

	switch(Oper){ 

		case AND_OPERATION:
			And_oper_imm(ARMProc,Dest,Src1,Src2);
			break;
		case EOR_OPERATION:
			eor_oper_imm(ARMProc,Dest,Src1,Src2);
			break;

		default:
			break;
	}


}
int tst_oper_reg(ARMProcState *ARMProc, unsigned int Src1, unsigned int Src2){

	unsigned int val = ARMProc->Reg[Src1] & ARMProc->Reg[Src2];

	ARMProc->NFlag = BIT(val,31);
	ARMProc->ZFlag = (val == 0 ? 1 : 0);


}


int rsc_oper_reg(ARMProcState *ARMProc, unsigned int Dest, unsigned int Src1, unsigned int Src2){

	ARMProc->Reg[Dest] = ARMProc->Reg[Src2] - ARMProc->Reg[Src1] - !(ARMProc->CFlag);

	if(ARMProc->SFlag){
		ARMProc->NFlag = BIT(ARMProc->Reg[Dest],31);
		ARMProc->ZFlag = (ARMProc->Reg[Dest] == 0 ? 1 : 0);
		set_sub_overflow(ARMProc,Src1,Src2,Dest);
		set_sub_carry(ARMProc,Src1,Src2,Dest);
	}

}

int sbc_oper_reg(ARMProcState *ARMProc, unsigned int Dest, unsigned int Src1, unsigned int Src2){
	ARMProc->Reg[Dest] = ARMProc->Reg[Src1] - ARMProc->Reg[Src2] - !(ARMProc->CFlag);
	
	if(ARMProc->SFlag){
		ARMProc->NFlag = BIT(ARMProc->Reg[Dest],31);
		ARMProc->ZFlag = (ARMProc->Reg[Dest] == 0 ? 1 : 0);
		set_sub_overflow(ARMProc,Src1,Src2,Dest);
		set_sub_carry(ARMProc,Src1,Src2,Dest);
	}
}

int adc_oper_reg(ARMProcState *ARMProc, unsigned int Dest, unsigned int Src1, unsigned int Src2){

	ARMProc->Reg[Dest] = ARMProc->Reg[Src1] + ARMProc->Reg[Src2] + ARMProc->CFlag;
	
	if(1 == ARMProc->SFlag){
		ARMProc->NFlag = BIT(ARMProc->Reg[Dest],31);
		ARMProc->ZFlag = (ARMProc->Reg[Dest] == 0 ? 1 : 0);
		set_add_carry(ARMProc,Src1,Src2,Dest);
		set_add_overflow(ARMProc,Src1,Src2,Dest);
	}
}


int add_oper_reg(ARMProcState *ARMProc, unsigned int Dest, unsigned int Src1, unsigned int Src2){ 
	
	ARMProc->Reg[Dest] = ARMProc->Reg[Src1] + ARMProc->Reg[Src2];

	if(1 == ARMProc->SFlag){ 
		ARMProc->NFlag = BIT(ARMProc->Reg[Dest],31);
		ARMProc->ZFlag = (ARMProc->Reg[Dest] == 0 ? 1 : 0);
		set_add_carry(ARMProc,Src1,Src2,Dest);
		set_add_overflow(ARMProc,Src1,Src2,Dest);
	}
}

int rsb_oper_reg(ARMProcState *ARMProc, unsigned int Dest, unsigned int Src1,unsigned int Src2){ 
}


int sub_oper_imm(ARMProcState *ARMProc, unsigned int Dest, unsigned int Src1,unsigned int Src2){ 


	ARMProc->Reg[Dest] = ARMProc->Reg[Src1] - Src2;

	if(1 == ARMProc->SFlag){ 
		ARMProc->NFlag = BIT(ARMProc->Reg[Dest],31);
		ARMProc->ZFlag = (ARMProc->Reg[Dest] == 0 ? 1 : 0);
	}

}


int sub_oper_reg(ARMProcState *ARMProc, unsigned int Dest, unsigned int Src1, unsigned int Src2){ 

	if(R15 == Dest){ 

	}
	else if(R13 == Dest){ 

	}
	else { 
		ARMProc->Reg[Dest] = ARMProc->Reg[Src1] - ARMProc->Reg[Src2];
		if(1 == ARMProc->SFlag){ 
			ARMProc->NFlag = BIT(ARMProc->Reg[Dest],31);
			ARMProc->ZFlag = (ARMProc->Reg[Dest] == 0 ? 1 : 0);
		}
	}

}


int eor_oper_reg(ARMProcState *ARMProc,unsigned int Dest, unsigned int Src1,unsigned int Src2){ 

	if(R15 == Dest){ 

	}
	else { 
		ARMProc->Reg[Dest] = ARMProc->Reg[Src1] ^ ARMProc->Reg[Src2];
		if(1 == ARMProc->SFlag){ 
			ARMProc->NFlag = BIT(ARMProc->Reg[Dest],31);
			ARMProc->ZFlag = (ARMProc->Reg[Dest] == 0 ? 1 : 0);
		}
	}

}

int eor_oper_imm(ARMProcState *ARMProc,unsigned int Dest, unsigned int Src1,unsigned int Src2){ 

	if(R15 == Dest){ 
	}
	else { 
		ARMProc->Reg[Dest] = ARMProc->Reg[Src1] ^ Src2;
		if(1 == ARMProc->SFlag){ 
			ARMProc->NFlag = BIT(ARMProc->Reg[Dest],31);
			ARMProc->ZFlag = (ARMProc->Reg[Dest] == 0 ? 1 : 0);
		}
	}
}


int And_oper_reg(ARMProcState *ARMProc,unsigned int Dest, unsigned int Src1,unsigned int Src2){ 
	if(R15 == Dest){ 

	}
	else { 
		ARMProc->Reg[Dest] = ARMProc->Reg[Src1] | ARMProc->Reg[Src2];
		
		if(1 == ARMProc->SFlag){ 
			ARMProc->NFlag = BIT(ARMProc->Reg[Dest],31);
			ARMProc->ZFlag = (ARMProc->Reg[Dest] == 0 ? 1 : 0);
		}
	}

	And_Oper_Debug(("And Result Reg : %d",ARMProc->Reg[Dest]));
	
	//CPSR Update
}

int And_oper_imm(ARMProcState *ARMProc,unsigned int Dest, unsigned int Src1,unsigned int Src2){ 

	if(R15 == Dest){ 
	}
	else{ 
		ARMProc->Reg[Dest] = ARMProc->Reg[Src1] | Src2;
		if(1 == ARMProc->SFlag){ 
			ARMProc->NFlag = BIT(ARMProc->Reg[Dest],31);
			ARMProc->ZFlag = (ARMProc->Reg[Dest] == 0 ? 1 : 0);
	
		}
	}
	And_Oper_Debug(("And Result Imm : %d",ARMProc->Reg[Dest]));
}



int Shift_Oper(ARMProcState* ARMProc,unsigned int Oper,unsigned int dst, int src, int mode){ 

	if(mode == SHIFT_IMM){
		Shift_Oper_Imm(ARMProc,Oper,dst,src);
	}

	else if(mode == SHIFT_REG){ 
		Shift_Oper_Reg(ARMProc,Oper,dst,src);
	}

	else { 
		ARM_Instr_Debug(("Wrong Mode in Shift Operation\n"));
	}

}

int Shift_Oper_Imm(ARMProcState* ARMProc,int Oper, unsigned int dst, unsigned int src){ 

	unsigned int tmp = 0;

	switch(Oper){ 

		case LSL_OPER:
			ARMProc->Reg[dst] = ARMProc->Reg[dst] << src;

			if(1 == ARMProc->SFlag){ 
				ARMProc->CFlag = ARMProc->Reg[dst] & 0x80000000;
			}
			
			break;

		case LSR_OPER:
			ARMProc->Reg[dst] = ARMProc->Reg[dst] >> src;
			if(1 == ARMProc->SFlag){ 
				ARMProc->CFlag = ARMProc->Reg[dst] & 0x80000000;
			}
			break;

		case ASR_OPER:
			ARMProc->Reg[dst] = (ARMProc->Reg[dst]|((ARMProc->Reg[dst] & 0x4fffffff) >> src));
			if(1 == ARMProc->SFlag){ 
				ARMProc->CFlag = ARMProc->Reg[dst] & 0x80000000;
			}
			break;

		case ROR_OPER:
			ARMProc->Reg[dst] = ((ARMProc->Reg[dst] >> src) | (BITS(ARMProc->Reg[dst],src,0) << (31 - src)));
			
			if(1 == ARMProc->SFlag){ 
				ARMProc->CFlag = ARMProc->Reg[dst] & 0x80000000;
			}

			break;

		case RRX_OPER:
			tmp = ARMProc->Reg[dst] & 1;
			ARMProc->Reg[dst] = (ARMProc->CFlag << 31) | (ARMProc->Reg[dst] >> 1);
			if(ARMProc->SFlag == 1){ 
				ARMProc->CFlag = tmp;
			}

			break;

		default:
			ARM_Instr_Debug(("Shift_Operation Imm  Exception : Oper : %d\n",Oper));
			break;
	}
}



int Shift_Oper_Reg(ARMProcState* ARMProc,int Oper, unsigned int dst, unsigned int src){ 

	switch(Oper){ 

		case LSL_OPER:
			ARMProc->Reg[dst] = ARMProc->Reg[dst] << ARMProc->Reg[src];
			break;

		case LSR_OPER:
			ARMProc->Reg[dst] = ARMProc->Reg[dst] >> ARMProc->Reg[src];
			break;

		case ASR_OPER:
			ARMProc->Reg[dst] = (ARMProc->Reg[dst]|((ARMProc->Reg[dst] & 0x4fffffff) >> ARMProc->Reg[src]));
			break;

		case ROR_OPER:
			ARMProc->Reg[dst] = ((ARMProc->Reg[dst] >> ARMProc->Reg[src]) | (BITS(ARMProc->Reg[dst],ARMProc->Reg[src],0) << (31 - ARMProc->Reg[src])));
			break;

		default:
			ARM_Instr_Debug(("Shift_Operation Reg  Exception : Oper : %d\n",Oper));
			break;
	}
}



int LShift_left_Oper(unsigned int dst, unsigned int src){ 
}

int LShift_Right_Oper(unsigned int dst, unsigned int src){ 
}

int AShift_Right_Oper(unsigned int dst, unsigned int src){ 
}

int Rotate_Right_Oper(unsigned int dst, unsigned int src){ 
}


int Rotate_Right_Ex_Oper(unsigned int dst,unsigned int src){ 
}
